#ifndef __OCTAVE_EXPORT_HH
#define __OCTAVE_EXPORT_HH
#include <iostream>
#include <fstream>
#include <stdlib.h>

#include "engine/Solution.hh"
#include "engine/ArrayList.hh"


using namespace std;

class OctaveExport {


private:

    static void mkdir(char *directory) {
        char* statement = new char[512];
        sprintf(statement, "mkdir -p %s", directory);
        system(statement);
        delete [] statement;
    }

    static bool exists(char *file) {
        ifstream stream(file);

        return !stream.fail();
    }

    static void run(ArrayList<Solution> *front, long elapsed_time, ofstream *octaveStream) {
        *octaveStream << "# Created by moe 1.0, this is the pareto front" << endl;
        *octaveStream << "# name: pareto_front" << endl;
        *octaveStream << "# type: matrix" << endl;
        *octaveStream << "# rows: " << front->length() << endl;
        *octaveStream << "# columns: " << Solution::getObjectivesLength() << endl;
        for (int i = 0; i < front->length(); i++) {
            Solution *solution = front->get(i);
            for (int j = 0; j < Solution::getObjectivesLength(); j++)
                *octaveStream << " " << solution->getObjectiveValue(j);
            *octaveStream << endl;
        }

        *octaveStream << "# name: elapsed_time" << endl;
        *octaveStream << "# type: scalar" << endl;
        *octaveStream << elapsed_time << endl;

        octaveStream->flush();
        delete octaveStream;
    }

    static ofstream *openStream(char *problem, char *rootDirectory, bool parallel) {
        char *directory = new char[512];

        if (parallel) sprintf(directory, "%s/%s/parallel", rootDirectory, problem);

        else sprintf(directory, "%s/%s/serial", rootDirectory, problem);

        mkdir(directory);

        char *fileName = new char[512];
        int i = 1;
        while (true) {
            sprintf(fileName, "%s/pareto_front_try_%d.data", directory, i);

            if (exists(fileName)) i++;

            else break;
        }

        ofstream *stream = new ofstream(fileName);

        delete [] directory;
        delete [] fileName;

        return stream;
    }

public:

    static void run(ArrayList<Solution> *front, char *problem, char *rootDirectory, long elapsed_time, bool parallel) {
        run(front, elapsed_time, openStream(problem, rootDirectory, parallel));
    }


};

#endif
